package com.fate.system.config;

import com.fate.system.constant.QuartzJobConst;
import com.fate.system.entity.QuartzJob;
import com.fate.system.service.IQuartzJobService;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.quartz.*;
import org.springframework.boot.context.event.ApplicationReadyEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.context.annotation.Configuration;

import java.util.List;

@Slf4j
@Configuration
public class SchedulerConfig implements ApplicationListener<ApplicationReadyEvent> {
  @Resource private IQuartzJobService quartzJobService;
  @Resource private Scheduler scheduler;

  @Override
  public void onApplicationEvent(ApplicationReadyEvent event) {
    try {
      // 获取所有启用状态的任务
      List<QuartzJob> jobs = quartzJobService.getRunJobList();

      for (QuartzJob job : jobs) {
        JobKey jobKey = JobKey.jobKey(job.getJobName(), job.getId());

        // 如果任务不存在，或状态为正常，则调度它
        if (QuartzJobConst.STATUS_NORMAL.equals(job.getStatus())
            && !scheduler.checkExists(jobKey)) {
          String jobClassName = job.getJobClassName().trim();
          String parameter = job.getParameter();
          JobDetail jobDetail =
              JobBuilder.newJob(getClass(jobClassName).getClass())
                  .withIdentity(jobClassName)
                  .usingJobData("parameter", parameter)
                  .build();

          Trigger trigger =
              TriggerBuilder.newTrigger()
                  .withIdentity(job.getJobName() + "Trigger", job.getId())
                  .withSchedule(CronScheduleBuilder.cronSchedule(job.getCronExpression()))
                  .build();

          scheduler.scheduleJob(jobDetail, trigger);
        }
      }
    } catch (SchedulerException | ClassNotFoundException e) {
      log.error("定时任务初始化失败", e);
    } catch (Exception e) {
      log.error(e.getMessage(), e);
    }
  }

  private static Job getClass(String classname) throws Exception {
    Class<?> class1 = Class.forName(classname);
    return (Job) class1.getDeclaredConstructor().newInstance();
  }
}
